package com.wenjie.login.annotations;


import com.wenjie.common.utils.TokenUtil;
import com.wenjie.original.entity.SysLogOper;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Pointcut;
import org.springframework.stereotype.Service;

import javax.servlet.http.HttpServletRequest;
import java.lang.reflect.Method;
import java.util.Date;

/**
 * @Author wenjie
 * @Date 2023/6/15
 * @Description: TODO 权限校验
 */
@Service
@Aspect
public class WJLongAspect {

    public static final String LOG_FLG = "LOG_FLG";
    public static final String LOG_START_TIME = "LOG_START_TIME";
    public static final String LOG_STATUS = "LOG_STATUS";

    public static final String LOG_METHOD = "LOG_METHOD";

    @Pointcut("@annotation(WJLong)")

    private void pointcut() {
    }


    /**
     * @Description: TODO 验证用户是否有权限
     * @Param:
     * @Return:
     * @Author: wenjie
     * @Date: 2023/6/16
     */
    @Around(value = "pointcut()")
    public Object boBefore(ProceedingJoinPoint joinPoint) throws Exception {
        HttpServletRequest request = TokenUtil.getRequest();

        try {

            // 获取到被调用的方法
            Method method = getMethodFromJoinPoint(joinPoint);
            if (method != null) {
                // 从方法上获取注解
                WJLong annotation = method.getAnnotation(WJLong.class);
                if (annotation != null) {
                    // 处理注解参数
                    String value = annotation.value();
                    request.setAttribute(LOG_FLG, value);
                    request.setAttribute(LOG_START_TIME, new Date().getTime());
                    request.setAttribute(LOG_METHOD, method.getName());
                }
            }

            // 执行目标方法并获取返回值
            Object result = joinPoint.proceed();

            // 方法执行后的逻辑
            request.setAttribute(LOG_STATUS, SysLogOper.STATUS.arg0);
            return result;
        } catch (Exception ex) {
            request.setAttribute(LOG_STATUS, SysLogOper.STATUS.arg1);
            throw ex;
        } catch (Throwable e) {
            request.setAttribute(LOG_STATUS, SysLogOper.STATUS.arg1);
            throw new RuntimeException(e);
        }


    }

    // 辅助方法，用于从 JoinPoint 获取方法
    private Method getMethodFromJoinPoint(JoinPoint joinPoint) {
        try {
            // 获取目标对象的所有方法
            Class<?> targetClass = joinPoint.getTarget().getClass();
            // 获取被调用的方法名称和参数类型
            String methodName = joinPoint.getSignature().getName();
            Class<?>[] parameterTypes = ((org.aspectj.lang.reflect.MethodSignature) joinPoint.getSignature()).getMethod().getParameterTypes();
            // 查找匹配的方法
            return targetClass.getMethod(methodName, parameterTypes);
        } catch (NoSuchMethodException e) {
            e.printStackTrace();
            return null;
        }
    }


}
